/**
 * axios封装
 * 请求拦截、响应拦截、错误统一处理
 */
import axios from 'axios';
import store from '../store';

// import { Message } from 'element-ui';
import Message from '../components/toast';

/**
 * 提示函数
 * 不显示关闭按钮、显示一秒后关闭
 */
const tip = (msg, duration) => {
    Message({
        message: msg,
        duration: duration
    });
};

/**
 * 跳转登录页
 * 携带当前页面路由，以期在登录页面完成登录后返回当前页面
 */
const toLogin = n => {
    if (top.location.href.indexOf('Login') == -1) {

        // sessionStorage.SRToken ? top.location.href = '/#/Index/noAccess?name=' + n : top.location.href = '/#/Login';
        sessionStorage.SRToken ?
            (window.location.href = '/APP/#/index/noAccess?name=' + n) :
            (window.location.href = '/APP/#/Login');
    }
};

/**
 * 请求失败后的错误统一处理
 * @param {Number} status 请求失败的状态码
 */
const errorHandle = (status, other) => {
    console.log(status);

    // 状态码判断
    switch (status) {
        case 401: // 403 token过期 清除token并跳转登录页
            if (window.sessionStorage.getItem('isSingleSignOn')) {
                window.location.href = '/loginOut.html';
            } else {
                toLogin(1);
            }
            break;
        case 403: // 403 拒绝访问接口 清除token并跳转无权限页面
            sessionStorage.removeItem('gw_token');
            store.commit('loginMsg', null);
            setTimeout(() => {
                toLogin(1);
            }, 1000);
            break;
        case 404:
            tip('请联系管理员更新服务接口', 3000);
            break;
        case 500: // ghost出现问题
            let url = other.config.url;
            if (
                url.indexOf('/IoT/api/v3/Auth/GetMenus') != -1 ||
                url.indexOf('IoT/api/v3/RealTime/GetRealTimeData') != -1
            ) {
                toLogin(2);
            }
            break;
        case 501:
            break;
        case 504:
            toLogin(2);
            break;
        default:

            // console.log(other);
            break;
    }
};

// 创建axios实例
let httpConfig = window.sessionStorage.httpConfig ? JSON.parse(window.sessionStorage.httpConfig) : {
    'countRetry': 0,
    'timeout': 30000,
    'retryDelay': 3000
};
let countRetry = httpConfig.countRetry;
let instance = axios.create({
    timeout: httpConfig.timeout,
    retry: countRetry,
    retryDelay: httpConfig.retryDelay
});

// 设置post请求头
instance.defaults.headers.post['Content-Type'] = 'application/json';

// instance.defaults.headers.post['Content-Type'] = 'application/x-www-form-urlencoded;charset=UTF-8';

/**
 * 请求拦截器
 * 每次请求前，如果存在token则在请求头中携带token
 */
instance.interceptors.request.use(
    config => {

        // 登录流程控制中，根据本地是否存在token判断用户的登录情况
        // 但是即使token存在，也有可能token是过期的，所以在每次的请求头中携带token
        // 后台根据携带的token判断用户的登录情况，并返回给我们对应的状态码
        // 而后我们可以在响应拦截器中，根据状态码进行一些统一的操作。
        const token = store.state.gwToken;
        token && (config.headers.Authorization = token);
        return config;
    },
    error => Promise.error(error)
);

let connectTimes = 0; // 统计连接次数，超过三次进入无权限页面

instance.interceptors.response.use(
    res => {
        console.log('----------------------------');
        console.log(res);
        console.log('----------------------------');
        if (res.status === 200 || res.status === 201 || res.status === 204) {
            let requestData = res.request;
            if (requestData.responseURL.indexOf('?ReturnUrl=') != -1) {
                toLogin(1);
                return;
            }
        }
        return res.status === 200 || res.status === 201 ?
            Promise.resolve(res) :
            Promise.reject(res);
    },
    function axiosRetryInterceptor(err) {
        console.log('--------------9999999999999--------------');
        console.log(err);
        console.log('--------------99999999999--------------');
        const { response } = err;
        if (response) {
            errorHandle(response.status, response);
            return Promise.reject(response);
        } else if (response == undefined) {
            let config = err.config;

            // If config does not exist or the retry option is not set, reject
            if (
                !config ||
                !config.retry ||
                config.url.indexOf('/api/ServiceManage/Reboot') != -1 ||
                config.url.indexOf('/api/v3/RealTime/GetRealTimeData') != -1
            ) {
                if (
                    config.url.indexOf('/api/v3/RealTime/GetRealTimeData') != -1
                ) {
                    tip('网络请求超时,请继续等待或者重新登录', 3000);
                }
                return Promise.reject(err);
            }

            // Set the variable for keeping track of the retry count
            config.__retryCount = config.__retryCount || 1;

            // Check if we've maxed out the total number of retries
            if (config.__retryCount > config.retry) {

                // hasConnect = false;
                return Promise.reject();
            }

            // Increase the retry count
            config.__retryCount += 1;

            // Create new promise to handle exponential backoff
            let backoff = new Promise(function(resolve) {
                setTimeout(function() {
                    resolve();
                }, config.retryDelay || 1);
            });

            // Return the promise in which recalls axios to retry the request
            return backoff.then(function() {
                connectTimes = connectTimes + 1;
                if (config.__retryCount == countRetry) {

                    // 重连两次之后连不上，进无权限页面
                    connectTimes = 0;
                }
                return instance(config);
            });
        }
    }
);

export default instance;